/*

* ------------------------------------------------------------------------
* ------------------------------------------------------------------------
* |     Smart-Shop开源商城系统/ Java商城-首选电商平台系统 请务必保留此注释头信息
* |     开源地址: https://gitee.com/ningbo-qishan/gruul-mall
* ------------------------------------------------------------------------
* ------------------------------------------------------------------------
* |     可正常分享和学习源码,未经授权 不可商用！
* |     商业版中台购买/开源版商业授权 联系技术客服
* |     官网:  https://www.73app.cn/
* ------------------------------------------------------------------------
* ------------------------------------------------------------------------
* |     Copyright (c) 2016-2999 宁波启山智软科技有限公司
* |     版权所有 ,侵权必究！
* ------------------------------------------------------------------------

*/
package com.medusa.gruul.goods.service.api.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollectionUtil;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.medusa.gruul.common.core.constant.CommonConstants;
import com.medusa.gruul.common.core.exception.ServiceException;
import com.medusa.gruul.common.core.util.CurUserUtil;
import com.medusa.gruul.common.core.util.Result;
import com.medusa.gruul.common.core.util.StringUtil;
import com.medusa.gruul.common.core.util.SystemCode;
import com.medusa.gruul.common.data.tenant.ShopContextHolder;
import com.medusa.gruul.common.data.tenant.TenantContextHolder;
import com.medusa.gruul.common.dto.CurShopInfoDto;
import com.medusa.gruul.common.dto.CurUserDto;
import com.medusa.gruul.discount.api.feign.RemoteDiscountService;
import com.medusa.gruul.discount.api.model.vo.api.ApiCouponVo;
import com.medusa.gruul.discount.api.model.vo.manager.FullScaleVo;
import com.medusa.gruul.goods.api.constant.GoodsConstant;
import com.medusa.gruul.goods.api.constant.GoodsProductSpecConst;
import com.medusa.gruul.goods.api.entity.Product;
import com.medusa.gruul.goods.api.entity.SaleMode;
import com.medusa.gruul.goods.api.model.param.api.ApiProductParam;
import com.medusa.gruul.goods.api.model.vo.api.ApiAliveProductVo;
import com.medusa.gruul.goods.api.model.vo.api.ApiProductVo;
import com.medusa.gruul.goods.api.model.vo.api.ApiShowCategoryProductVo;
import com.medusa.gruul.goods.api.model.vo.api.ApiShowCategoryVo;
import com.medusa.gruul.goods.mapper.api.*;
import com.medusa.gruul.goods.service.api.IApiProductService;
import com.medusa.gruul.goods.service.manager.IProductSpecService;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.*;

/**
 * 小程序商品信息 服务实现类
 *
 * @author kyl
 * @since 2019-10-06
 */
@Service
public class ApiProductServiceImpl extends ServiceImpl<ApiProductMapper, Product> implements IApiProductService {

    @Autowired
    private ApiProductMapper productMapper;

    @Autowired
    private ApiProductSkuMapper apiProductSkuMapper;

    @Autowired
    private ApiAliveProductMapper apiAliveProductMapper;

    @Autowired
    private ApiShowCategoryMapper apiShowCategoryMapper;

    @Autowired
    private ApiSaleModeMapper apiSaleModeMapper;

    @Resource
    private RemoteDiscountService remoteDiscountService;

    @Autowired
    private IProductSpecService productSpecService;


    /**
     * 根据主键id查询商品详情
     *
     * @param id 商品id
     * @return 商品信息
     */
    @Override
    public ApiProductVo getProductById(Long id) {
        ApiProductVo apiProductVo = productMapper.queryByPrimaryKey(id);
        if (BeanUtil.isEmpty(apiProductVo)) {
            throw new ServiceException("商品不存在！", SystemCode.DATA_EXISTED.getCode());
        }
        apiProductVo.setProductSpecs(productSpecService.getProductSpecs(id, GoodsProductSpecConst.SPEC_GROUP_PARENT_ID));
        return apiProductVo;
    }

    /**
     * 商品分页列表
     *
     * @param apiProductParam 商品查询条件
     * @return 分页对象
     */
    @Override
    public IPage<ApiAliveProductVo> getPageList(ApiProductParam apiProductParam) {
        IPage<ApiAliveProductVo> apiAliveProductVoIPage = new Page<>(apiProductParam.getCurrent(), apiProductParam.getSize());
        List<ApiAliveProductVo> aliveProductVos = apiAliveProductMapper.querySuperMarketProductList(apiAliveProductVoIPage, apiProductParam);
        return apiAliveProductVoIPage.setRecords(aliveProductVos);


    }

    /**
     * 字符串ids转List<Long>集合公共方法
     *
     * @param filterProductIds 字符串
     * @return List<Long>
     */
    private List<Long> getProductTypeAndIdList(String filterProductIds) {
        if (StringUtil.isNotEmpty(filterProductIds)) {
            List<Long> productIds = new ArrayList<>(filterProductIds.split(",").length);
            Arrays.asList(filterProductIds.split(",")).forEach(str -> {
                if (StringUtil.isNotEmpty(str)) {
                    productIds.add(Long.parseLong(str.trim()));
                }
            });
            return productIds;
        } else {
            return new ArrayList<>(CommonConstants.NUMBER_ZERO);
        }
    }




    /**
     * 商超系统分类列表
     *
     * @param apiProductParam 商品查询条件
     * @return 分页对象
     */
    @Override
    public IPage<ApiAliveProductVo> getSupermarketList(ApiProductParam apiProductParam) {
        IPage<ApiAliveProductVo> apiAliveProductVoIPage = new Page<>(apiProductParam.getCurrent(), apiProductParam.getSize());
        List<ApiAliveProductVo> aliveProductVos = apiAliveProductMapper.querySuperMarketProductList(apiAliveProductVoIPage, apiProductParam);
        return apiAliveProductVoIPage.setRecords(aliveProductVos);
    }

    /**
     * 获取单张客户已领取优惠券可使用商品列表
     *
     * @param productType     0-全部商品参与  1-指定商品参与  2-指定商品不参与
     * @param productIds
     * @param apiProductParam
     * @return IPage<ApiAliveProductVo>
     */
    @Override
    public List<ApiAliveProductVo> findAliveProductByMemberCoupon(Integer productType, List<Long> productIds, String apiProductParam) {
        ApiProductParam param = new ApiProductParam();
        if (StringUtils.isNotBlank(apiProductParam)) {
            param = JSON.parseObject(apiProductParam, ApiProductParam.class);
        }
        IPage<ApiAliveProductVo> page = new Page<>(param.getCurrent(), param.getSize());
        return apiAliveProductMapper.queryProductList(page, param, productType, productIds);
    }





    //=============================================满减、优惠劵部分===================================================

    /**
     * 商品详情获取可使用优惠劵信息
     *
     * @param productId 商品id
     * @return 客户优惠劵信息
     */
    @Override
    public List<ApiCouponVo> getCouponByProductId(Long productId) {
        CurUserDto curUserDto = CurUserUtil.getHttpCurUser();
        if (curUserDto == null){
            return Collections.emptyList();
        }
        String userId = curUserDto.getUserId();
        List<ApiCouponVo> apiCouponVos = remoteDiscountService.findCouponListForProduct(userId, productId);
        return apiCouponVos;
    }

    /**
     * 商品详情获取可使用满减活动信息
     *
     * @param productId 商品id
     * @return 满减活动信息
     */
    @Override
    public List<FullScaleVo> getFullScaleByProductId(Long productId) {
        List<FullScaleVo> fullScaleVos = remoteDiscountService.findFullScaleListForProduct(productId);
        return fullScaleVos;
    }

    //=============================================商品组件根据商品集合匹配未删除的商品===================================================

    /**
     * 根据商品数组匹配未删除的商品
     *
     * @param ids
     * @param launchArea
     * @param saleMode
     * @return List<DiscountProductVo>
     */
    @Override
    public List<ApiAliveProductVo> getAliveProductList(Long[] ids, String launchArea, Long saleMode) {
        List<ApiAliveProductVo> aliveProductVos = apiAliveProductMapper.querySaveProductList(Arrays.asList(ids), saleMode);
        return aliveProductVos;
    }

    //=============================================接龙服务获取接龙商品信息===================================================

    /**
     * 获取接龙活动的商品信息
     *
     * @param productType      0-全部商品参与  1-指定商品参与  2-指定商品不参与
     * @param productIds
     * @param distributionMode
     * @param current
     * @param size
     * @return List<ApiProductVo>
     */
    @Override
    public IPage<ApiProductVo> getSolitaireActivityProductByParam(Integer productType, Long[] productIds, Integer distributionMode, Integer current, Integer size) {
        IPage<ApiProductVo> page = new Page<>(current, size);
        log.debug("productType=" + productType + "productIds=" + productIds.toString() + "distributionMode=" + distributionMode + "current=" + current + "size=" + size);
        return page.setRecords(apiProductSkuMapper.querySolitaireActivityProductByParam(page, productType, productIds, distributionMode));
    }

    /**
     * 获取接龙活动的商品信息
     *
     * @param productType 0-全部商品参与  1-指定商品参与  2-指定商品不参与
     * @param productIds
     * @return List<ApiProductVo>
     */
    @Override
    public List<ApiProductVo> getSolitaireActivityProduct(Integer productType, List<Long> productIds) {
        return this.baseMapper.querySolitaireActivityProduct(productType, productIds);
    }

    //=============================================商品分类页组件根据商品分类集合匹配对应分类下的商品===================================================

    /**
     * pc商品分类集合匹配对应分类下的商品
     *
     * @param ids
     * @return List<DiscountProductVo>
     */
    @Override
    public List<ApiShowCategoryProductVo> getAliveProductListGroupByCategory(Long[] ids) {
        List<Long> idList = Arrays.asList(ids);
        List<ApiShowCategoryVo> apiShowCategoryVos = apiShowCategoryMapper.queryAllApiShowCategoryList();
        List<ApiShowCategoryProductVo> apiShowCategoryProductVos = new ArrayList<>(apiShowCategoryVos.size());
        if (CollectionUtil.isNotEmpty(apiShowCategoryVos)) {
            apiShowCategoryVos.stream().forEach(apiShowCategoryVo -> {
                if (idList.contains(apiShowCategoryVo.getId()) && CollectionUtil.isNotEmpty(apiShowCategoryVo.getShowCategoryVos())) {
                    apiShowCategoryVo.getShowCategoryVos().stream().forEach(apiShowCategorySecondVo -> {
                        List<ApiAliveProductVo> aliveProductVos = apiAliveProductMapper.queryShowCategoryProductList(apiShowCategorySecondVo.getId());
                        if (CollectionUtil.isNotEmpty(aliveProductVos)) {
                            ApiShowCategoryProductVo apiShowCategoryProductVo = new ApiShowCategoryProductVo();
                            apiShowCategoryProductVo.setId(apiShowCategorySecondVo.getId());
                            apiShowCategoryProductVo.setName(apiShowCategorySecondVo.getName());
                            apiShowCategoryProductVo.setApiAliveProductVos(aliveProductVos);
                            apiShowCategoryProductVos.add(apiShowCategoryProductVo);
                        }
                    });
                }
            });
        }
        return apiShowCategoryProductVos;
    }

    /**
     * 小程序商品分类集合匹配对应分类下的商品
     *
     * @param ids
     * @param saleMode
     * @return List<DiscountProductVo>
     */
    @Override
    public List<ApiShowCategoryProductVo> getAliveProductListByCategory(Long[] ids, Long saleMode) {
        SaleMode saleModeSearch = apiSaleModeMapper.selectOne(new QueryWrapper<SaleMode>().eq("id", saleMode));
        if (BeanUtil.isEmpty(saleModeSearch)) {
            return new ArrayList<>(CommonConstants.NUMBER_ZERO);
        }
        List<Long> idList = Arrays.asList(ids);

        List<ApiShowCategoryVo> apiShowCategoryVos;
        apiShowCategoryVos = apiShowCategoryMapper.queryApiSupermarketShowCategoryList(saleMode);
        List<ApiShowCategoryProductVo> apiShowCategoryProductVos = new ArrayList<>(apiShowCategoryVos.size());
        if (CollectionUtil.isNotEmpty(apiShowCategoryVos)) {
            apiShowCategoryVos.stream().forEach(apiShowCategoryVo -> {
                //判断是否有二级分类并且在过滤的一级分类下
                if (idList.contains(apiShowCategoryVo.getId()) && CollectionUtil.isNotEmpty(apiShowCategoryVo.getShowCategoryVos())) {
                    apiShowCategoryVo.getShowCategoryVos().stream().forEach(apiShowCategorySecondVo -> {
                        List<ApiAliveProductVo> aliveProductVos = apiAliveProductMapper.queryShowCategoryProductListBySaleMode(apiShowCategorySecondVo.getId(), saleMode);
                        if (CollectionUtil.isNotEmpty(aliveProductVos)) {
                            ApiShowCategoryProductVo apiShowCategoryProductVo = new ApiShowCategoryProductVo();
                            apiShowCategoryProductVo.setId(apiShowCategorySecondVo.getId());
                            apiShowCategoryProductVo.setName(apiShowCategorySecondVo.getName());
                            apiShowCategoryProductVo.setApiAliveProductVos(aliveProductVos);
                            apiShowCategoryProductVos.add(apiShowCategoryProductVo);
                        }
                    });
                }
            });
        }
        return apiShowCategoryProductVos;

    }
}
